﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Net.Sockets;
using System.Net;
using Domain.NetworkService.Behaviors.Interfaces;

namespace Domain.NetworkService
{
    public class TcpTestBehavior : INetworkServiceTest
    {
        public TcpPorts port {get; private set;}
        IPAddress ip;
        
        public TcpTestBehavior(IPAddress ip, TimeSpan timeout, TcpPorts port)
        {
            this.port = port;
            this.ip = ip;
            this.Timeout = timeout;

            Description = new Description()
            {
                networkTestDescription = NetworkTestDescription.TCP,
                Special = port,
                Timeout = timeout,
                HostNameOrIP = ip.ToString()
            };
        }

        public NetworkTestResult Start()
        {
            SocketError socketError = SocketError.Success;
            if (isPortOpen(ref socketError))
            {
                return new TcpResult()
                {
                    IP = ip,
                    Port = port,
                    Status = ResultStatus.Success,
                    Info = socketError,
                    VarDateTime = DateTime.Now
                };
            }
            else
            {
                return new TcpResult()
                {
                    IP = ip,
                    Port = port,
                    Status = ResultStatus.Failed,
                    Info = socketError,
                    VarDateTime = DateTime.Now
                };
            }
        }

        private bool isPortOpen(ref SocketError socketError)
        {
            using (TcpClient client = new TcpClient())
            {
                try
                {
                    client.Connect(ip, (int)port);
                }
                catch (SocketException se)
                {
                    foreach (SocketError sError in Enum.GetValues(typeof(SocketError)))
                    {
                        if (se.SocketErrorCode == sError)
                        {
                            socketError = sError;
                        }
                    }
                    return false;
                }
                client.Close();
                return true;
            }
        }
        public IDescription Description { get; set; }
        public TimeSpan Timeout { get; set; }
    }
}
